NULL() 
	return 0;
end;

VALUE(p) 
	return p[0];
end;

LEFT(p)
	return p[1];
end;

RIGHT(p) 
	return p[2];
end;

SETLEFT(p,n)
	p[1] = n;
	return 0;
end;

SETRIGHT(p,n) 
	p[2] = n;
	return 0;
end;

ENTRY(p,size,i)
	return p+(size*i);
end;

treesort(data,size,length,dst)
	buildtree(data,size,length);
	traversetree(data,dst,0);
end;

traversetree(node,dst,index)
	if (node!=NULL()) goto continue;
	return 0;
	continue:
	var x=index;
	x = x + traversetree(LEFT(node),dst,x);
	dst[x] = VALUE(node);
	x = x + 1;
	x = x + traversetree(RIGHT(node),dst,x);
	return x + (-index);
end;

buildtree(data,length,size)
	var i=1;
	var head = ENTRY(data,size,0);
	doLoop:
	if not (length>i) goto doneLoop;
	var entry = ENTRY(data,size,i);
	treeadd(head,entry);
	i = i+1;
	goto doLoop;
	doneLoop:
	return 0;
end;

treeadd(node,new)
	if (VALUE(new)>VALUE(node)) goto testright;
	testleft:
		if (LEFT(node)!=NULL()) goto recleft;
		insleft:
			SETLEFT(node,new);
			return 0;
		recleft:
			treeadd(LEFT(node),new);
			return 0;
	testright:
		if (RIGHT(node)!=NULL()) goto recright;
		insright:
			SETRIGHT(node,new);
			return 0;
		recright:
			treeadd(RIGHT(node),new);
			return 0;
end;
